package com.uxsino.simo.query;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

import com.uxsino.commons.utils.config.PropElement;
import com.uxsino.reactorq.model.IndicatorValue;
import com.uxsino.simo.indicator.CompoundIndicator;
import com.uxsino.simo.indicator.expression.ExprEvaluator;
import com.uxsino.simo.utils.ConfigLoadingContext;

public class CompoundMergeQueryCombine extends QueryCombine<CompoundIndicator, Map<String, Object>> {

    public CompoundMergeQueryCombine(CompoundIndicator resultIndicator) {
        super(resultIndicator);
    }

    @Override
    public Map<String, Object> apply(QueryContext ctxt, List<IndicatorValue> values) {
        HashMap<String, Object> r = new HashMap<>();

        for (IndicatorValue iv : values) {
            if (iv.value instanceof Map) {
                @SuppressWarnings("unchecked")
                Map<String, Object> mvalue = (Map<String, Object>) iv.value;
                // r.putAll(mvalue);
                mergeMap(r, mvalue);
            }
        }
        ExprEvaluator ev = ctxt.getExprEvaluator(values.get(0).entityId);
        for (IndicatorValue ind : values) {
            ev.evalExprFields(ctxt.getDepo().getIndicatorNamespace().getIndicator(ind.indicatorName), r);
        }
        return r;
    }

    @Override
    public String getQueryType() {
        return "merge";
    }

    @Override
    public void loadProp(PropElement eCombine, ConfigLoadingContext lctxt) {

    }

    private void mergeMap(HashMap<String, Object> totalMap, Map<String, Object> map) {
        for (Map.Entry<String, Object> entry : map.entrySet()) {
            if (!totalMap.containsKey(entry.getKey()) || totalMap.get(entry.getKey()) == null) {
                totalMap.put(entry.getKey(), entry.getValue());
            }
        }
    }

    @Override
    public boolean isCustom() {
        return false;
    }

}
